<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta http-equiv="X-UA-Compatible" content="IE=edge">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>工厂模式-ES5</title>
</head>
<body>
    
</body>
<script>
    //工厂模式(Factory Pattern)
    //工厂模式：根据不同的输入返回不同类的实例，一般用来创建同一类对象。
    //工厂方式的主要思想是将对象的创建与对象的实现分离。

    //工厂模式的使用场景:
    //1.对象的创建比较复杂，而访问者无需知道创建的具体流程
    //2.处理大量具有相同属性的小对象

    //工厂模式的优缺点
    //优点:工厂模式将 对象的创建和实现分离。
        //1.良好的封装，代码结构清晰，访问者无需知道对象的创建流程，特别是创建比较复杂的情况下
        //2.扩展性优良，通过工厂方法隔离了用户和创建流程隔离，符合开放封闭原则
        //3.解耦了高层逻辑和底层产品类，符合最少知识原则，不需要的就不要去交流
    //缺点:带来了额外的系统复杂度，增加了抽象性

    // 拓展
    // 工厂模式与模板方法模式的主要区别是：
    // 1.工厂模式主要关注产品实例的创建，对创建流程封闭起来
    // 2.模板方法模式 主要专注的是为固定的算法骨架提供某些步骤的实现

    //经典点菜
    function restaurant(menu){
        switch(menu){
            case '鱼香肉丝': return new YuXiangRouSi();
            case '宫保鸡丁': return new GongBaoJiDing();
            default: throw new Error('这个菜本店没有')
        }
    }

    function YuXiangRouSi(){
        this.type='鱼香肉丝'
    }
    YuXiangRouSi.prototype.eat=function(){
        console.log(this.type+'真香')
    }

    function GongBaoJiDing(){
        this.type='宫保鸡丁'
    }
    GongBaoJiDing.prototype.eat=function(){
        console.log(this.type+'让我想起了老家的菜')
    }

    const dish1=restaurant('宫保鸡丁')
    dish1.eat()
    const dish2=restaurant('红烧排骨')
    // Error:这个菜本店没有
</script>
</html>